﻿using SafeLoad.NControl.Assist;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Media;
using System.Windows.Shapes;

namespace SafeLoad.NControl
{
    /// <summary>
    /// wpf专用的辅助工具类
    /// </summary>
    public class WpfUtils
    {
        public static Line DrawLine(Canvas canvas, Point point1, Point point2, Color color, double thickness)
        {
            return DrawLine(canvas, point1.X, point1.Y, point2.X, point2.Y, color, thickness);
        }

        public static Line DrawLine(Canvas canvas, double x1, double y1, double x2, double y2, Color color, double thickness)
        {
            return DrawLine(canvas, x1, y1, x2, y2, new SolidColorBrush(color), thickness);
        }

        public static Line DrawLine(Canvas canvas, double x1, double y1, double x2, double y2, Brush brush, double thickness)
        {
            Line line = new Line();
            line.X1 = x1;
            line.Y1 = y1;
            line.X2 = x2;
            line.Y2 = y2;
            line.StrokeThickness = thickness;
            line.Stroke = brush;
            canvas.Children.Add(line);
            return line;
        }


        public static Line DrawLine(Canvas canvas, double x1, double y1, double x2, double y2, Color color, double thickness, double[] dashArray)
        {
            Line line = new Line();
            line.X1 = x1;
            line.Y1 = y1;
            line.X2 = x2;
            line.Y2 = y2;
            line.StrokeDashArray = new DoubleCollection(dashArray);
            line.StrokeThickness = thickness;
            line.Stroke = new SolidColorBrush(color);
            canvas.Children.Add(line);
            return line;
        }

        public static Ellipse DrawEllipse(Canvas canvas, double x, double y, double width, double height, Color color, double thickness)
        {
            Ellipse ellipse = new Ellipse();
            ellipse.Width = width;
            ellipse.Height = height;
            canvas.Children.Add(ellipse);
            Canvas.SetLeft(ellipse, x);
            Canvas.SetTop(ellipse, y);
            ellipse.StrokeThickness = thickness;
            ellipse.Stroke = new SolidColorBrush(color);
            return ellipse;
        }

        public static Rectangle DrawRect(Canvas canvas, Rect rect, Color color, double thickness)
        {
            Rectangle r = new Rectangle();
            r.Width = rect.Width;
            r.Height = rect.Height;
            canvas.Children.Add(r);
            Canvas.SetLeft(r, rect.Left);
            Canvas.SetTop(r, rect.Top);
            r.StrokeThickness = thickness;
            r.Stroke = new SolidColorBrush(color);
            return r;
        }

        public static Rectangle DrawRect(Canvas canvas, System.Drawing.RectangleF rect, Color color, double thickness)
        {
            Rectangle r = new Rectangle();
            r.Width = rect.Width;
            r.Height = rect.Height;
            canvas.Children.Add(r);
            Canvas.SetLeft(r, rect.Left);
            Canvas.SetTop(r, rect.Top);
            r.StrokeThickness = thickness;
            r.Stroke = new SolidColorBrush(color);
            return r;
        }

        #region Fill Rectangle

        public static Rectangle FillRectangle(Canvas canvas, double x, double y, double width, double height, Brush brush)
        {
            if (width >= 0 && height >= 0)
            {
                Rectangle ellipse = new Rectangle();
                ellipse.Width = width;
                ellipse.Height = height;
                canvas.Children.Add(ellipse);
                Canvas.SetLeft(ellipse, x);
                Canvas.SetTop(ellipse, y);
                ellipse.Fill = brush;
                return ellipse;
            }
            return null;
        }

        public static Rectangle FillRectangle(Canvas canvas, System.Drawing.RectangleF rect, Color color)
        {
            Rectangle r = new Rectangle();
            r.Width = rect.Width;
            r.Height = rect.Height;
            canvas.Children.Add(r);
            Canvas.SetLeft(r, rect.Left);
            Canvas.SetTop(r, rect.Top);
            r.Fill = new SolidColorBrush(color);
            return r;
        }

        public static Rectangle FillRectangle(Rectangle rect, Color color)
        {
            rect.Fill = new SolidColorBrush(color);
            return rect;
        }

        #endregion

        #region Fill Ellipse

        public static Ellipse FillEllipse(Canvas canvas, double x, double y, double width, double height, Color color)
        {
            return FillEllipse(canvas, x, y, width, height, new SolidColorBrush(color));
        }

        public static Ellipse FillEllipse(Canvas canvas, double x, double y, double width, double height, Brush brush)
        {
            Ellipse ellipse = new Ellipse();
            ellipse.Width = width;
            ellipse.Height = height;
            canvas.Children.Add(ellipse);
            Canvas.SetLeft(ellipse, x);
            Canvas.SetTop(ellipse, y);
            ellipse.Fill = brush;
            return ellipse;
        }

        #endregion

        public static Polyline DrawLines(Canvas canvas, Point[] points, Color color, double thickness, double[] dashArray = null)
        {
            Polyline polylines = new Polyline();
            polylines.Points = new PointCollection(points);
            polylines.StrokeThickness = thickness;
            polylines.Stroke = new SolidColorBrush(color);
            if (dashArray != null)
                polylines.StrokeDashArray = new DoubleCollection(dashArray);
            canvas.Children.Add(polylines);
            return polylines;
        }

        public static void DrawLines(Canvas canvas, Point[] points, NCurveItem line, int pointsRadius)
        {
            if (points.Length < 2) return;

            if (line.Style == CurveStyle.LineSegment || line.Style == CurveStyle.Curve)
            {
                DrawLines(canvas, points, line.LineColor, line.LineThickness);
            }
            else if (line.Style == CurveStyle.LineDot)
            {
                DrawLines(canvas, points, line.LineColor, line.LineThickness, new double[] { 1, 1 });
            }
            else if (line.Style == CurveStyle.StepLine)
            {
                PointCollection collects = new PointCollection();
                for (int i = 0; i < points.Length - 1; i++)
                {
                    Point center = new Point(points[i + 1].X, points[i].Y);
                    collects.Add(points[i]);
                    collects.Add(center);
                }

                collects.Add(points[points.Length - 1]);
                DrawLines(canvas, collects.ToArray(), line.LineColor, line.LineThickness);
            }
            else
            {
                for (int i = 0; i < points.Length - 1; i++)
                {
                    Point center = new Point(points[i + 1].X, points[i].Y);
                    Line line1 = new Line();
                    line1.X1 = points[i].X;
                    line1.Y1 = points[i].Y;
                    line1.X2 = center.X;
                    line1.Y2 = center.Y;
                    line1.StrokeThickness = line.LineThickness;
                    line1.Stroke = new SolidColorBrush(line.LineColor);
                    canvas.Children.Add(line1);
                }
            }

            if (pointsRadius > 0 && pointsRadius < 20)
            {
                for (int i = 0; i < points.Length; i++)
                {
                    FillEllipse(canvas, points[i].X - pointsRadius, points[i].Y - pointsRadius, pointsRadius * 2, pointsRadius * 2, line.LineColor);
                }
            }
        }

        public static Path DrawCurve(Canvas canvas, Point[] points, Color color, double thickness)
        {
            Path path = new Path();
            path.StrokeThickness = thickness;
            path.Stroke = new SolidColorBrush(color);
            canvas.Children.Add(path);
            return path;
        }

        public static Polygon FillPolygon(Canvas canvas, Point[] points, Color color)
        {
            return FillPolygon(canvas, points, new SolidColorBrush(color));
        }

        public static Polygon FillPolygon(Canvas canvas, Point[] points, Brush brush)
        {
            Polygon polygon = new Polygon();
            polygon.Points = new PointCollection(points);
            polygon.Fill = brush;
            canvas.Children.Add(polygon);
            return polygon;
        }

        public static Polygon DrawPolygon(Canvas canvas, Point[] points, Color color, float penWidth)
        {
            Polygon polygon = new Polygon();
            polygon.Points = new PointCollection(points);
            polygon.StrokeThickness = penWidth;
            polygon.Stroke = new SolidColorBrush(color);
            canvas.Children.Add(polygon);
            return polygon;
        }

        public static Polygon FillTriangle(Canvas canvas, Point point, Color color, int size, GraphDirection direction)
        {
            Point[] points = new Point[4];
            if (direction == GraphDirection.Leftward)
            {
                points[0] = new Point(point.X, point.Y - size);
                points[1] = new Point(point.X, point.Y + size);
                points[2] = new Point(point.X - 2 * size, point.Y);
            }
            else if (direction == GraphDirection.Rightward)
            {
                points[0] = new Point(point.X, point.Y - size);
                points[1] = new Point(point.X, point.Y + size);
                points[2] = new Point(point.X + 2 * size, point.Y);
            }
            else if (direction == GraphDirection.Upward)
            {
                points[0] = new Point(point.X - size, point.Y);
                points[1] = new Point(point.X + size, point.Y);
                points[2] = new Point(point.X, point.Y - 2 * size);
            }
            else
            {
                points[0] = new Point(point.X - size, point.Y);
                points[1] = new Point(point.X + size, point.Y);
                points[2] = new Point(point.X, point.Y + 2 * size);
            }

            points[3] = points[0];
            return FillPolygon(canvas, points, color);
        }

        public static void DrawString(Canvas canvas, string text, Color color, double x, double y, double width, double height, HorizontalAlignment horizontal, VerticalAlignment vertical)
        {
            DrawString(canvas, text, new SolidColorBrush(color), x, y, width, height, horizontal, vertical);
        }

        public static void DrawString(Canvas canvas, string text, Brush foreground, double x, double y, double width, double height, HorizontalAlignment horizontal, VerticalAlignment vertical)
        {
            Label label = new Label();
            label.Width = width;
            label.Height = height;
            label.Foreground = foreground;
            label.HorizontalContentAlignment = horizontal;
            label.VerticalContentAlignment = vertical;
            label.Content = text;
            canvas.Children.Add(label);
            label.Style = null;
            Canvas.SetLeft(label, x);
            Canvas.SetTop(label, y);
        }

        public static void DrawString(Canvas canvas, string text, Brush foreground, double fontSize, double x, double y, double width, double height, HorizontalAlignment horizontal, VerticalAlignment vertical)
        {
            Label label = new Label();
            label.Width = width;
            label.Height = height;
            label.FontSize = fontSize;
            label.Foreground = foreground;
            label.HorizontalContentAlignment = horizontal;
            label.VerticalContentAlignment = vertical;
            label.Content = text;
            canvas.Children.Add(label);
            Canvas.SetLeft(label, x);
            Canvas.SetTop(label, y);
        }
    }
}
